﻿// ------------------------------------------------------------------------------
// <copyright file="XamlMember.cs" company="skumaronline.com">
//    Copyright (C) 2012 Suresh Kumar T.  All rights reserved.
// </copyright>
// ------------------------------------------------------------------------------

namespace StoreAppLib.MetaData
{
    using System;
    using Windows.UI.Xaml.Markup;

    /// <summary>
    /// XAML member
    /// </summary>
    [System.CodeDom.Compiler.GeneratedCodeAttribute("Microsoft.Windows.UI.Xaml.Build.Tasks", "4.0.0.0")]
    [System.Diagnostics.DebuggerNonUserCodeAttribute]
    public sealed class XamlMember : IXamlMember
    {
        /// <summary>
        /// XAML type information provider
        /// </summary>
        private XamlTypeInfoProvider provider;

        /// <summary>
        /// XAML name string that declares the XAML member
        /// </summary>
        private string name;

        /// <summary>
        /// Indicates whether the XAML member is an attachable member
        /// </summary>
        private bool isAttachable;

        /// <summary>
        /// Indicates whether the XAML member is implemented as a dependency
        /// </summary>
        private bool isDependencyProperty;

        /// <summary>
        /// Indicates whether XAML member is read-only in its backing implementation
        /// </summary>
        private bool isReadOnly;

        /// <summary>
        /// The XAML type of the member
        /// </summary>
        private string typeName;

        /// <summary>
        /// The target type name
        /// </summary>
        private string targetTypeName;

        /// <summary>
        /// Initializes a new instance of the <see cref="XamlMember"/> class"
        /// </summary>
        /// <param name="provider">The XAML information provider</param>
        /// <param name="name">XAML name string that declares the XAML member</param>
        /// <param name="typeName">The XAML type of the member</param>
        public XamlMember(XamlTypeInfoProvider provider, string name, string typeName)
        {
            this.name = name;
            this.typeName = typeName;
            this.provider = provider;
        }

        /// <summary>
        /// Gets the XAML name string that declares the XAML member
        /// </summary>
        public string Name
        {
            get
            {
                return this.name;
            }
        }

        /// <summary>
        /// Gets the XAML type of the type that is used by the member
        /// </summary>
        public IXamlType Type
        {
            get
            {
                return this.provider.GetXamlTypeByName(this.typeName);
            }
        }

        /// <summary>
        /// Gets a value indicating whether the XAML member is an attachable member
        /// </summary>
        public bool IsAttachable
        {
            get
            {
                return this.isAttachable;
            }
        }

        /// <summary>
        /// Gets a value indicating whether the XAML member is implemented as a dependency
        /// </summary>
        public bool IsDependencyProperty
        {
            get
            {
                return this.isDependencyProperty;
            }
        }

        /// <summary>
        /// Gets or sets Getter
        /// </summary>
        public Getter Getter { get; set; }

        /// <summary>
        /// Gets or sets Setter
        /// </summary>
        public Setter Setter { get; set; }

        /// <summary>
        /// Gets the XAML name string that declares the XAML member
        /// </summary>
        public IXamlType TargetType
        {
            get
            {
                return this.provider.GetXamlTypeByName(this.targetTypeName);
            }
        }

        /// <summary>
        /// Gets a value indicating whether the XAML member is read-only in its backing implementation
        /// </summary>
        public bool IsReadOnly
        {
            get
            {
                return this.isReadOnly;
            }
        }

        /// <summary>
        /// Sets whether the XAML member is read-only in its backing implementation
        /// </summary>
        public void SetIsReadOnly()
        {
            this.isReadOnly = true;
        }

        /// <summary>
        /// Sets target type name
        /// </summary>
        /// <param name="targetTypeName">Target type name</param>
        public void SetTargetTypeName(string targetTypeName)
        {
            this.targetTypeName = targetTypeName;
        }

        /// <summary>
        /// Gets the value
        /// </summary>
        /// <param name="instance">The instance</param>
        /// <returns>Returns the value</returns>
        public object GetValue(object instance)
        {
            if (Getter != null)
            {
                return Getter(instance);
            }
            else
            {
                throw new InvalidOperationException("GetValue");
            }
        }

        /// <summary>
        /// Sets value to instance
        /// </summary>
        /// <param name="instance">The instance</param>
        /// <param name="value">The value</param>
        public void SetValue(object instance, object value)
        {
            if (Setter != null)
            {
                Setter(instance, value);
            }
            else
            {
                throw new InvalidOperationException("SetValue");
            }
        }

        /// <summary>
        /// Sets a value that indicates whether the XAML member is implemented as a dependency
        /// </summary>
        public void SetIsDependencyProperty()
        {
            this.isDependencyProperty = true;
        }

        /// <summary>
        /// Sets a value that indicates whether the XAML member is an attachable member
        /// </summary>
        public void SetIsAttachable()
        {
            this.isAttachable = true;
        }
    }
}
